#include "EnemyPhase.h"

cEnemyPhase::cEnemyPhase(cInfoUnion *InfoUnion,
						 cInputDevice *InputDevice,
						 cCharacterHandler *CharacterHandler,
						 cMyCursor *Cursor,cFightScene *FightScene,
						 cRangeHoney *RangeHoney,cBlockHandler *BlockHandler)
{
	s_InfoUnion = InfoUnion;
	s_InputDevice = InputDevice;
	s_Cursor = Cursor;
	s_FightScene = FightScene;
	s_CharacterHandler = CharacterHandler;
	s_BlockHandler = BlockHandler;
	s_RangeHoney = RangeHoney;
	
	m_ProcCharacter = NULL;
	s_BackFocus = NULL;
	m_AIMoveAndAtk = NULL;

	InitProc();
}

cEnemyPhase::~cEnemyPhase(void)
{
	if (m_AIMoveAndAtk!=NULL)
	{
		delete m_AIMoveAndAtk;
		m_AIMoveAndAtk = NULL;
	}
}

BOOL cEnemyPhase::Execute(unsigned char *keystate, BOOL *locks, int ex)
{
	if (m_EProc.empty())
	{
		return MY_ENEMY_PHASE_EXIT;
	}

	switch(m_EProc.front())
	{
	case EP_ChooseCharacter:
		if (m_NPCs.empty())
		{
			return MY_ENEMY_PHASE_EXIT;
		}
		m_ProcCharacter = m_NPCs.back();
		m_NPCs.pop_back();

		m_EProc.pop_front();
		break;

	case EP_SetCamera:
		{
			assert(m_ProcCharacter!=NULL);
			int ScrMatrixNumX = s_InfoUnion->ScrMatrixNumX;
			int ScrMatrixNumY = s_InfoUnion->ScrMatrixNumY;

			s_InfoUnion->CameraPosX = (m_ProcCharacter->GetMatrixPosX()-ScrMatrixNumX/2)*s_InfoUnion->MatrixUnitWidth;
			s_InfoUnion->CameraPosY = (m_ProcCharacter->GetMatrixPosY()-ScrMatrixNumY/2)*s_InfoUnion->MatrixUnitHeight;

			m_EProc.pop_front();
		}
		break;

	case EP_SelectCharacterAction:
		{
			bool IfFillCon = false;
			map<int,cCharUnitAI> *OrderAI = m_ProcCharacter->GetOrderAI();
			map<int,cCharUnitAI>::iterator iter = OrderAI->begin();
			for (;iter!=OrderAI->end();iter++)
			{
				switch ((*iter).second.Condition)
				{
				case AC_HPMore90Percent:
					if (m_ProcCharacter->GetDataHP()/m_ProcCharacter->GetDataMaxHP() >= 0.9f)
					{
						m_CurrentBeh = (*iter).second.Behavior;
						IfFillCon = true;
					}
					break;

				case AC_HPMore80Percent:
					if (m_ProcCharacter->GetDataHP()/m_ProcCharacter->GetDataMaxHP() >= 0.8f)
					{
						m_CurrentBeh = (*iter).second.Behavior;
						IfFillCon = true;
					}
					break;

				default:
					break;
				}
				if (IfFillCon == true)
				{
					break;
				}
			}
			if (IfFillCon == false)
			{
				m_CurrentBeh = AB_Standby;
			}
		}
		m_EProc.pop_front();
		break;

	case EP_DoAction:
		
		switch (m_CurrentBeh)
		{
		case AB_Standby:
			m_EProc.pop_front();
			break;

		case AB_MoveAndAttak:
			
			if (m_AIMoveAndAtk == NULL)
			{
				m_AIMoveAndAtk = new cAIMoveAndAtk(s_InfoUnion,
					s_FightScene,s_InputDevice,s_RangeHoney,s_BlockHandler,s_CharacterHandler);
				m_AIMoveAndAtk->InitProc();
				m_AIMoveAndAtk->SetFocusNPC(m_ProcCharacter);
				m_AIMoveAndAtk->SetPlayers(&m_Players);
			}
			if (m_AIMoveAndAtk->Run() == AI_DONE)
			{
				delete m_AIMoveAndAtk;
				m_AIMoveAndAtk = NULL;
				m_EProc.pop_front();
			}

			break;

		case AB_MoveLeftOneSetp:
			m_ProcCharacter->SetMatrixPosX(m_ProcCharacter->GetMatrixPosX()-1);
			m_EProc.pop_front();
			break;

		case AB_MoveUpOneStep:
			m_ProcCharacter->SetMatrixPosY(m_ProcCharacter->GetMatrixPosY()-1);
			m_EProc.pop_front();
			break;

		default:
			m_EProc.pop_front();
			break;
		}

		break;

	default:
		break;
	}

	return MY_ENEMY_PHASE_DEFAULT;
}

BOOL cEnemyPhase::ReceiveDirective(int message)
{
	return TRUE;
}

void cEnemyPhase::SetBackFocus(cMyFocus *focus)
{
	this->s_BackFocus = focus;
}

cMyFocus *cEnemyPhase::GetBackFocus()
{
	return s_BackFocus;
}

void cEnemyPhase::InitProc()
{
	m_NPCs.clear();
	m_Players.clear();
	vector<cMyCharacter*> *AllCharacters = s_CharacterHandler->GetCharacters();
	vector<cMyCharacter*>::iterator iter = AllCharacters->begin();
	for (;iter!=AllCharacters->end();iter++)
	{
		if ((*iter)->GetCharacterType()==CHAR_TYPE_NPC)
		{
			m_NPCs.push_back(*iter);
		}
		if ((*iter)->GetCharacterType()==CHAR_TYPE_PLAYER)
		{
			m_Players.push_back(*iter);
		}
	}

	m_EProc.clear();
	m_EProc.push_back(EP_ChooseCharacter);
	m_EProc.push_back(EP_SetCamera);
	m_EProc.push_back(EP_SelectCharacterAction);
	m_EProc.push_back(EP_DoAction);
}